#include <string.h>
#include <stdio.h>
#include <Includes.h>
#include <EC600S_AT/AT.h>
#include <DRV_EC600S.h>
#include <DRV_EC600S_Sock.h>
#include <DRV_EC600S_Usim.h>
#include <OPP_Debug.h>
#include <AT_Urc.h>
//#include <SVS_Time.h>
//#include <SVS_Mqtt.h>

//字符child在string中个数
int strcount(char *string, char *child)
{
    char *str;
    int count=0;

    str=string;
    while(1)
    {
        str=strstr(str,child);
        if(str)
        {
            count++;
			if(strlen(str)<strlen(child))
				break;
			str+=strlen(child);
        }
        else
        {
            break;
        }
    }
    return count;
}

//字符child在string第n次出现的位置
int strloc(char *string, char *child, int n, char **p)
{
    char *str;
    int cnt=0;

	str=string;
    while(1)
    {
        str=strstr(str,child);
        if(!str)
        {
            return 1;
        }
        if(++cnt==n)
        {
            *p=str;
            break;
        }
		str+=strlen(child);
    }

    return 0;
}

int UrcDebug(char *inBuffer,int bufLen)
{
    //根据需要选择二进制还是字符打印,注意二进制用%s打印乱码,
    //DEBUG_LOG(DEBUG_MODULE_URCS, DLL_DEBUG,  "len:%d,%s\r\n",bufLen,inBuffer);
    StringDump(DEBUG_MODULE_URCS,"URC",inBuffer,bufLen);
    DataDump(DEBUG_MODULE_URCB, "URC", (U8 *)inBuffer, bufLen);
    return 0;
}

/*split URC msg*/
int Ec600sUrcMsgProc(char *inBuffer,int bufLen)
{
	char *str = NULL,*ptr=NULL;
	U8 reg;
	int inLen = bufLen;
	int ret = 0;
    int sock,contextID,err,zone;
    static U8 attBeginMark=0,attEndMark=0;

    //进环形缓存处理黏包
    ret=Ec600sRBWrite(inBuffer,inLen);

	while(1){
        UrcDebug(inBuffer,inLen);
        //简单格式匹配
		if(!strstr(inBuffer,"\r\nRDY")
			&& !strstr(inBuffer,"\r\nPOWERED DOWN")
			&& !strstr(inBuffer,"\r\nNORMAL POWER DOWN")
			&& !strstr(inBuffer,"\r\n+CPIN: READY")
			&& !strstr(inBuffer,"\r\n+CPIN: NOT INSERTED")
			&& !strstr(inBuffer,"\r\n+CTZV:")
			&& !strstr(inBuffer,"\r\n+QIOPEN:")
			&& !strstr(inBuffer,"\r\n+QIURC: \"closed\"")
			&& !strstr(inBuffer,"\r\n+QIURC: \"recv\"")
			&& !strstr(inBuffer,"\r\n+QIURC: \"incoming full\"")
			&& !strstr(inBuffer,"\r\n+QIURC: \"incoming\"")
			&& !strstr(inBuffer,"\r\n+QIURC: \"pdpdeact\"")
			&& !strstr(inBuffer,"\r\n+QMTOPEN:")
			&& !strstr(inBuffer,"\r\n+QMTCLOSE:")
			&& !strstr(inBuffer,"\r\n+QMTCONN:")
			&& !strstr(inBuffer,"\r\n+QMTDISC:")
			&& !strstr(inBuffer,"\r\n+QMTSUB:")
			&& !strstr(inBuffer,"\r\n+QMTUNS:")
			&& !strstr(inBuffer,"\r\n+QMTPUBEX:")
			&& !strstr(inBuffer,"\r\n+QMTSTAT:")
			&& !strstr(inBuffer,"\r\n+QMTRECV:")
			&& !strstr(inBuffer,"\r\n+QMTPING:"))
	    {
            //复杂格式匹配[+CGREG: 0,0],不处理
            str = strstr(inBuffer, "\r\n+CGREG:");
            if(str)
            {
                if(strchr(str, ','))
			        break;
            }
            else
            {
                break;
            }
		}

        //http下载固件,固件包会带ec600s保留字段,优先处理QIURC消息
        str = strstr(inBuffer, "\r\n+QIURC: \"recv\"");
        if(str)
        {
            /*char tmp[64]={0};

            ret=sscanf(str,"%*[^,],%[^\r\n]",tmp);
            if(ret==1)
            {
                int count=strcount(tmp,",");
                //recv缓存模式
                if(count==0)
                {
                    ret=sscanf(tmp,"%d",&sock);
                    if(ret==1)
                    {
                        Ec600sSockHasDataSet(sock,1);
                    }
                }
                //recv直吐模式
                else if(count==1)
                {
                    ret=sscanf(tmp,"%d,%d",&sock,&length);
                    if(ret==2)
                    {
                        //替换第一个\r\n为两个空格s
                        ptr = strstr(str+2,"\r\n");
                        if(ptr)
                        {
                            //拷贝数据
                            memcpy(data,ptr+2,length);
                            Ec600sDataDump(data, length);

                            Ec600sSockUrcCallback(sock,data,length);

                            *ptr=' ';
                            *(ptr+1)=' ';
                            memset(ptr+2,' ',length);
                        }
                    }
                }
            }*/
            URC_FILTER(inBuffer,inLen,str,"\r\n+QIURC: \"recv\"","\r\n");
        }

		str = strstr(inBuffer, "\r\nRDY");
		if(str)
		{
            //记录附着开始tick
            if(attBeginMark==0)
            {
                attBeginMark=1;
                DASetAttachStartTime();
            }
            Ec600sStSet(EC600S_DEV_PWRON);
			URC_FILTER(inBuffer,inLen,str,"\r\nRDY","\r\n");
		}
		str = strstr(inBuffer, "\r\n+CGREG:");
		if(str && NULL==strchr(str, ','))
		{
			ret = sscanf(str, "\r\n+CGREG:%hhu%*[\r\n]", &reg);
			if(1 == ret){
                if(reg==1||reg==5)
                {
                    //记录附着结束tick
                    if(attEndMark==0)
                    {
                        attEndMark=1;
                        DASetAttachEndTime();
                    }
                    Ec600sStSet(EC600S_DEV_READY);
                }
				if(reg < INVALID_REG)
				{
					Ec600sRegStSet((EN_REG_STATE)reg);
                }
			}
			URC_FILTER(inBuffer,inLen,str,"\r\n+CGREG:","\r\n");
		}

        //do nothing
		str = strstr(inBuffer, "\r\nNORMAL POWER DOWN");
        if(str)
        {
			URC_FILTER(inBuffer,inLen,str,"\r\nNORMAL POWER DOWN","\r\n");
        }

		str = strstr(inBuffer, "\r\nPOWERED DOWN");
        if(str)
        {
            //测试模式下不再复位EC600S
            if(Ec600sStGet()!=EC600S_DEV_TEST)
                Ec600sStSet(EC600S_DEV_WAIT_PWROFF);

            //更新套接字状态
            Ec600sSockStUpdate();
            Ec600sUsimStSet(USIM_UNKNOW);
			URC_FILTER(inBuffer,inLen,str,"\r\nPOWERED DOWN","\r\n");
        }

		str = strstr(inBuffer, "\r\n+CPIN: READY");
        if(str)
        {
            Ec600sUsimStSet(USIM_READY);
			URC_FILTER(inBuffer,inLen,str,"\r\n+CPIN: READY","\r\n");
        }

		str = strstr(inBuffer, "\r\n+CPIN: NOT INSERTED");
        if(str)
        {
            Ec600sUsimStSet(USIM_NOT_INSERT);
			URC_FILTER(inBuffer,inLen,str,"\r\n+CPIN: NOT INSERTED","\r\n");
        }

		str = strstr(inBuffer, "\r\n+CTZV:");
        if(str)
        {
            ret=sscanf(str,"%*[^\"]\"%d\"%*[^\r\n]",&zone);
            if(ret==1)
            {
                //zone noted by wangtao
                //set_zone(zone/4);
            }
			URC_FILTER(inBuffer,inLen,str,"\r\n+CTZV:","\r\n");
        }

		str = strstr(inBuffer, "\r\n+QIOPEN:");
        if(str)
        {
            ret=sscanf(str,"\r\n%*[^:]:%d,%d%*[\r\n]",&sock,&err);
            if(ret==2)
            {
                if(err==0)
                {
                    Ec600sSockStSet(sock,SS_CONNECTED);
                }
                else
                {
                    Ec600sSockStSet(sock,SS_DISCONNECTING);
                }
                Ec600sQIOPENTo(sock,err==0?err:1);
            }
			URC_FILTER(inBuffer,inLen,str,"\r\n+QIOPEN:","\r\n");
        }

		str = strstr(inBuffer, "\r\n+QIURC: \"closed\"");
        if(str)
        {
            ret=sscanf(str,"\r\n%*[^,],%d%*[\r\n]",&sock);
            if(ret==1)
            {
                Ec600sSockStSet(sock,SS_DISCONNECTING);
            }
			URC_FILTER(inBuffer,inLen,str,"\r\n+QIURC: \"closed\"","\r\n");
        }

		str = strstr(inBuffer, "\r\n+QIURC: \"incoming full\"");
        if(str)
		{
			URC_FILTER(inBuffer,inLen,str,"\r\n+QIURC: \"incoming full\"","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QIURC: \"incoming\"");
        if(str)
		{
			URC_FILTER(inBuffer,inLen,str,"\r\n+QIURC: \"incoming\"","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QIURC: \"pdpdeact\"");
        if(str)
		{
            ret=sscanf(str,"\r\n%*[^,],%d%*[\r\n]",&contextID);
            if(ret==1)
            {
                if(Ec600sStGet()>EC600S_DEV_WAIT_PWRON)
                {
                    Ec600sAT_QIDEACT_QIN(contextID);
                }
                //WAIT_PWRON阶段收到+QIURC: "pdpdeact"设备起不来需要再复位次
                if(Ec600sStGet()==EC600S_DEV_WAIT_PWRON
                    ||Ec600sStGet()==EC600S_DEV_WAIT_PWROFF)
                {
                    //测试模式下不再复位EC600S
                    if(Ec600sStGet()!=EC600S_DEV_TEST)
                    {
                        Ec600sStSet(EC600S_DEV_WAIT_PWROFF);
                        Ec600sTPwrOffReCountDown();
                    }
                }
            }
			URC_FILTER(inBuffer,inLen,str,"\r\n+QIURC: \"pdpdeact\"","\r\n");
        }
//mqtt noted by wangtao        
#if 0
		str = strstr(inBuffer, "\r\n+QMTOPEN:");
        if(str)
        {
            ST_MQTT_OPEN_CFM_EVENT_PARA para;
            int a,b,c;

            ret=sscanf(str,"%*[^:]:%d,%d,%d%*[^\r\n]",&a,&b,&c);
            if(ret==2)
            {
                para.client_idx=a;
                para.result=b;
                MqttCB(EVENT_MQTT_OPEN_CFM, &para);
            }
            else
            {
                //AT+QMTOPEN?返回-QMTOPEN:<client_idx>,<host_name>,<port>
                str[2]='-';
            }
            URC_FILTER(inBuffer,inLen,str,"\r\n+QMTOPEN:","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QMTCLOSE:");
        if(str)
        {
            ST_MQTT_CLOSE_CFM_EVENT_PARA para;
            ret=sscanf(str,"%*[^:]:%d,%d%*[^\r\n]",&para.client_idx,&para.result);
            if(ret==2)
            {
                MqttCB(EVENT_MQTT_CLOSE_CFM, &para);
            }
            else
            {
                //AT+QMTCLOSE=?返回-QMTCLOSE: (支持的<client_idx>范围)
                str[2]='-';
            }
            URC_FILTER(inBuffer,inLen,str,"\r\n+QMTCLOSE:","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QMTCONN:");
        if(str)
        {
            ST_MQTT_CONN_CFM_EVENT_PARA para;
            int a,b,c;

            ret=sscanf(str,"%*[^:]:%d,%d,%d%*[^\r\n]",&a,&b,&c);
            if(ret==3)
            {
                para.client_idx=a;
                para.result=b;
                para.ret_code=c;
                MqttCB(EVENT_MQTT_CONN_CFM, &para);
            }
            else
            {
                //AT+QMTCONN=?返回-QMTCONN: (支持的<client_idx>范围),"clientid","username","password"
                //AT+QMTCONN?返回-QMTCONN:<client_idx>,<state>
                str[2]='-';
            }
            URC_FILTER(inBuffer,inLen,str,"\r\n+QMTCONN:","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QMTDISC:");
        if(str)
        {
            ST_MQTT_DISC_CFM_EVENT_PARA para;
            ret=sscanf(str,"%*[^:]:%d,%d%*[^\r\n]",&para.client_idx,&para.result);
            if(ret==2)
            {
                MqttCB(EVENT_MQTT_DISC_CFM, &para);
            }
            else
            {
                //AT+QMTDISC=?返回-QMTDISC: (支持的<client_idx>范围)
                str[2]='-';
            }
            URC_FILTER(inBuffer,inLen,str,"\r\n+QMTDISC:","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QMTSUB:");
        if(str)
        {
            ST_MQTT_SUB_CFM_EVENT_PARA para={.value={-1}};
            char tmp[32]={0};
            char buf[32]={0};
            char *ptr1;

            //只提取+QMTSUB urc字段
            ret=sscanf(str,"%*[^:]:%[^\r\n]",tmp);
            if(ret==1)
            {
                if(strcount(tmp, ",")==2)
                {
                    ret=sscanf(tmp,"%d,%hd,%d",&para.client_idx,&para.msgid,&para.result);
                    if(ret==3)
                    {
                        MqttCB(EVENT_MQTT_SUB_CFM, &para);
                    }
                }
                else if(strcount(tmp, ",")>2)
                {
                    ret=sscanf(tmp,"%d,%hd,%d%*[^,]",&para.client_idx,&para.msgid,&para.result);
                    if(ret==3)
                    {
                        if(para.result==0)
                        {
                            for(int i=0;i<TOPIC_NUM;i++)
                            {
                                if(0==strloc(tmp,",",3+i,&ptr))
                                {
                                    if(0==strloc(tmp,",",3+i+1,&ptr1))
                                    {
                                        strncpy(buf,ptr+1,ptr1-ptr-1);
                                        para.value[i]=atoi(buf);
                                    }
                                    //解析最后一个字符
                                    else
                                    {
                                        strcpy(buf,ptr+1);
                                        para.value[i]=atoi(buf);
                                        MqttCB(EVENT_MQTT_SUB_CFM, &para);
                                    }
                                }
                            }
                        }
                        else if(para.result==1)
                        {
                            ret=sscanf(tmp,"%d,%hd,%d,%d",&para.client_idx,&para.msgid,&para.result,&para.value[0]);
                            if(ret==4)
                            {
                                MqttCB(EVENT_MQTT_SUB_CFM, &para);
                            }
                        }
                    }
                    else
                    {
                        //AT+QMTSUB=?返回-QMTSUB: ( 支 持 的 <client_idx> 范 围 ),<msgid>,list of["topic",qos]
                        str[2]='-';
                    }
                }
            }
			URC_FILTER(inBuffer,inLen,str,"\r\n+QMTSUB:","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QMTUNS:");
        if(str)
        {
            ST_MQTT_UNS_CFM_EVENT_PARA para={.value={-1}};
            char tmp[32]={0};
            char buf[32]={0};
            char *ptr1;

            //只提取+QMTUNS urc字段
            ret=sscanf(str,"%*[^:]:%[^\r\n]",tmp);
            if(ret==1)
            {
                if(strcount(tmp, ",")==2)
                {
                    ret=sscanf(tmp,"%d,%hd,%d",&para.client_idx,&para.msgid,&para.result);
                    if(ret==3)
                    {
                        MqttCB(EVENT_MQTT_UNS_CFM, &para);
                    }
                    else
                    {
                        //AT+QMTUNS=?返回-QMTUNS: ( 支 持 的 <client_idx> 范 围 ),<msgid>,list of[<topic>]
                        str[2]='-';
                    }
                }
                else if(strcount(tmp, ",")>2)
                {
                    ret=sscanf(tmp,"%d,%hd,%d%*[^,]",&para.client_idx,&para.msgid,&para.result);
                    if(ret==3)
                    {
                        if(para.result==0)
                        {
                            for(int i=0;i<TOPIC_NUM;i++)
                            {
                                if(0==strloc(tmp,",",3+i,&ptr))
                                {
                                    if(0==strloc(tmp,",",3+i+1,&ptr1))
                                    {
                                        strncpy(buf,ptr+1,ptr1-ptr-1);
                                        para.value[i]=atoi(buf);
                                    }
                                    //解析最后一个字符
                                    else
                                    {
                                        strcpy(buf,ptr+1);
                                        para.value[i]=atoi(buf);
                                        MqttCB(EVENT_MQTT_UNS_CFM, &para);
                                    }
                                }
                            }
                        }
                        else if(para.result==1)
                        {
                            ret=sscanf(tmp,"%d,%hd,%d,%d",&para.client_idx,&para.msgid,&para.result,&para.value[0]);
                            if(ret==4)
                            {
                                MqttCB(EVENT_MQTT_UNS_CFM, &para);
                            }
                        }
                    }
                }
            }
			URC_FILTER(inBuffer,inLen,str,"\r\n+QMTUNS:","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QMTPUBEX:");
        if(str)
        {
            ST_MQTT_PUBEX_CFM_EVENT_PARA para={.value=-1};
            ret=sscanf(str,"%*[^:]:%d,%hd,%d,%d%*[^\r\n]",&para.client_idx,&para.msgid,&para.result,&para.value);
            if(ret==3||ret==4)
            {
                MqttCB(EVENT_MQTT_PUBEX_CFM, &para);
            }
            else
            {
                //AT+QMTPUBEX=?返回-QMTPUBEX: (支持的<client_idx>范围),<msgid>,(支持的<qos>范围),(支持的<retain>列表),"topic","length"
                str[2]='-';
            }
            URC_FILTER(inBuffer,inLen,str,"\r\n+QMTPUBEX:","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QMTSTAT:");
        if(str)
        {
            ST_MQTT_STAT_EVENT_PARA para;
            ret=sscanf(str,"%*[^:]:%d,%d%*[^\r\n]",&para.client_idx,&para.err_code);
            if(ret==2)
            {
                MqttCB(EVENT_MQTT_STAT, &para);
            }
			URC_FILTER(inBuffer,inLen,str,"\r\n+QMTSTAT:","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QMTRECV:");
        if(str)
        {
            ST_MQTT_RCV_EVENT_PARA para;

            ret=sscanf(str,"%*[^:]:%d,%hd,\"%[^\"]\",%d%*[^,]",&para.client_idx,&para.msgid,para.topic,&para.payload_len);
            if(ret==4)
            {
                /*if(0==strloc(str,"\"",3,&ptr))
                {
                    memcpy(para.payload,ptr+1,para.payload_len);
                    MqttCB(EVENT_MQTT_RECV, &para);
                }*/
            }
            else
            {
                //AT+QMTRECV?返回-QMTRECV: <client_idx>,<store_status_0>,<store_status_1>,<store_status_2>,<store_status_3>,<store_status_4>
                str[2]='-';
            }
            URC_FILTER(inBuffer,inLen,str,"\r\n+QMTRECV:","\r\n");
        }
		str = strstr(inBuffer, "\r\n+QMTPING:");
        if(str)
        {
            ST_MQTT_PING_EVENT_PARA para;
            ret=sscanf(str,"%*[^:]:%d,%d%*[^\r\n]",&para.client_idx,&para.result);
            if(ret==2)
            {
                MqttCB(EVENT_MQTT_PING, &para);
            }

			URC_FILTER(inBuffer,inLen,str,"\r\n+QMTPING:","\r\n");
        }
#endif
	}
	return inLen;
}

